#ifndef XLCOMM_NET_RPCCLIENT_H_
#define XLCOMM_NET_RPCCLIENT_H_

#include <functional>
#include <map>

#include "boost/any.hpp"
#include "xlcomm/net/rpc/rpc.h"
#include "xlcomm/net/rpc/rpc_codec.h"
#include "xlcomm/net/tcp_client.h"
#include "xlcomm/noncopyable.h"

namespace xlcomm {
namespace net {

class RpcClient : noncopyable {
 public:
  using RpcResponseCallback = std::function<void(
      const RpcParamReader& resReader, RpcErrorCode errcode)>;

  RpcClient(EventLoop* loop, const InetAddress& server_addr);

  void Connect() { client_.Connect(); }
  void Disconnect() { client_.Disconnect(); }

  // bool SyncCall(const std::string& service, const std::string& method,
  //               const RpcMessage* request, RpcMessage* response,
  //               int timeout_ms = 0);

  bool AsyncCall(const std::string& service, const std::string& method,
                 const net::RpcParam& reqParam,
                 const RpcResponseCallback& res_callback);

 private:
  void OnRpcResult(const TcpConnectionPtr& conn, RpcMeta& meta);

  TcpClient client_;
  RpcCodec codec_;
  std::map<int64_t, RpcResponseCallback> pendings_;
};

}  // namespace net
}  // namespace xlcomm

#endif  // XLCOMM_NET_RPCCLIENT_H_